#include <func.h>

#define BACKLOG 10
#define MAXEVENTS 1024  // 可根据实际调整 

int tcp_listen(const char* port) {
    struct addrinfo hints, *res, *p;

    bzero(&hints, sizeof(hints));
    hints.ai_family = AF_UNSPEC;
    hints.ai_socktype = SOCK_STREAM;
    hints.ai_flags = AI_PASSIVE;    // wildcard address

    int rv;
    if ((rv = getaddrinfo(NULL, port, &hints, &res)) != 0) {
        error(1, rv, "getaddrinfo: %s", gai_strerror(rv));
    }

    // loop through all the results and bind to the first we can
    int sockfd;
    for (p = res; p != NULL; p = p->ai_next) {
        if ((sockfd = socket(p->ai_family, p->ai_socktype, p->ai_protocol)) == -1) {
            error(0, errno, "socket failed");
            continue;
        }
        int yes = 1;
        if (setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, &yes, sizeof(yes)) == -1) {
            error(1, errno, "setsockopt");
        }
        if (bind(sockfd, p->ai_addr, p->ai_addrlen) == -1) {
            error(0, errno, "bind");
            continue;
        }
        break;
    }
    freeaddrinfo(res); // all done with this structure
    if (p == NULL) {
        error(1, 0, "failed to bind");
    }
    if (listen(sockfd, BACKLOG) == -1) {
        error(1, errno, "listen");
    }
    return sockfd;
}

int main(int argc,char* argv[])
{
    int listenfd = tcp_listen("10086");

    int connfd = accept(listenfd, NULL, NULL);
    printf("INFO: 接收连接成功\n");

    // 接收文件的名字
    int length;
    recv(connfd, &length, sizeof(int), MSG_WAITALL);

    char path[1024];
    recv(connfd, path, length, MSG_WAITALL);
    printf("path: %s", path);

    // 接收文件内容
    int fd = open("b.txt", O_WRONLY | O_CREAT | O_TRUNC, 0666);
    char buf[4096];
    int n;
    while ((n = recv(connfd, buf, 4096, 0)) > 0) {
        write(fd, buf, n);
    }

    close(fd);
    close(connfd);
    return 0;
}
